#!/bin/bash
set -euo pipefail

# Uncomment the line below if you would like to diagnose what commands are being done on your behalf.
# set -x

DEFAULT_POSTGRES_HOST="localhost"
DEFAULT_POSTGRES_USER=""
DEFAULT_POSTGRES_PASSWORD=""
DEFAULT_POSTGRES_DATABASE="rustodon"
DATABASE_URL="${DATABASE_URL:-""}"

infoMsg() {
  echo "[*] ${1}"
}

alertMsg() {
  echo "[!] ${1}" >&2
}

# Ensure rustup and rust are installed
if which rustup 2>/dev/null 1>&2 ; then
  NIGHTLY_VERSION="$(cat rust-toolchain)"
  infoMsg "Setting Rust version to ${NIGHTLY_VERSION}..."
  # Ensure that rust is using nightly for library features
  rustup override set "${NIGHTLY_VERSION}" 2>/dev/null 1>&2
else
  # Installation deferred to user
  alertMsg "You must install rust and rustup, see: https://www.rust-lang.org/en-US/install.html and https://rustup.rs/"
  exit 1
fi

if ! rustup component list | grep rustfmt-preview | grep installed 2>/dev/null 1>&2 ; then
  infoMsg "Installing rustfmt..."
  rustup component add rustfmt-preview
fi

# Ensure Postgres is installed
if ! which psql 2>/dev/null 1>&2 ; then
  # Installation deferred to user
  alertMsg "You must install Postgres, see: https://www.postgresql.org/download/"
  exit 1
fi

# Ensure SASS is installed
if ! which sass 2>/dev/null 1>&2 ; then
  # Installation deferred to user
  alertMsg "You must install SASS, see: https://sass-lang.com/install"
  exit 1
fi

# Don't track changes to .env
git update-index --assume-unchanged .env

if [ -z "${DATABASE_URL}" ]; then
  if ! grep DATABASE_URL ./.env 2>/dev/null 1>&2; then
    # Prompt user for local database information
    read -p "Postgres host (default: ${DEFAULT_POSTGRES_HOST}): " POSTGRES_HOST
    read -p "Postgres user (default: ${DEFAULT_POSTGRES_USER}): " POSTGRES_USER
    read -p "Postgres password (default: ${DEFAULT_POSTGRES_PASSWORD}): " POSTGRES_PASSWORD
    read -p "Postgres database (default: ${DEFAULT_POSTGRES_DATABASE}): " POSTGRES_DATABASE
    if [ -z "${POSTGRES_HOST}" ]; then
      POSTGRES_HOST="${DEFAULT_POSTGRES_HOST}"
    fi
    if [ -z "${POSTGRES_USER}" ]; then
      POSTGRES_USER="${DEFAULT_POSTGRES_USER}"
    fi
    if [ -z "${POSTGRES_PASSWORD}" ]; then
      POSTGRES_PASSWORD="${DEFAULT_POSTGRES_PASSWORD}"
    fi
    if [ -z "${POSTGRES_DATABASE}" ]; then
      POSTGRES_DATABASE="${DEFAULT_POSTGRES_DATABASE}"
    fi
    DB_CREDENTIALS=""
    if [ ! -z "${POSTGRES_USER}" ]; then
      if [ -z "${POSTGRES_PASSWORD}" ]; then
        DB_CREDENTIALS="${POSTGRES_USER}@"
      else
        DB_CREDENTIALS="${POSTGRES_USER}:${POSTGRES_PASSWORD}@"
      fi
    fi
    if [ -z "${POSTGRES_PASSWORD}" ]; then
      DATABASE_URL="postgres://${DB_CREDENTIALS}${POSTGRES_HOST}/${POSTGRES_DATABASE}"
    else
      DATABASE_URL="postgres://${DB_CREDENTIALS}${POSTGRES_HOST}/${POSTGRES_DATABASE}"
    fi
    infoMsg "Database URL is ${DATABASE_URL}"
    echo "DATABASE_URL=${DATABASE_URL}" >> .env
  else
    source .env
  fi
fi

# Diesel CLI install
if ! which diesel 2>/dev/null 1>&2 ; then
  infoMsg "Installing diesel_cli..."
  cargo install diesel_cli --no-default-features --features="postgres"
fi
if ! which cargo-watch 2>/dev/null 1>&2 ; then
  infoMsg "Installing cargo-watch..."
  cargo install cargo-watch
fi
if ! which fors 2>/dev/null 1>&2 ; then
  infoMsg "Installing fors..."
  cargo install fors
fi

# Database creation and migration
infoMsg "Running migrations..."
diesel database setup --migration-dir=migrations

if [ ! -f "Rocket.toml" ]; then
  infoMsg "Generating Rocket.toml. This contains your server secret key, keep this file private."
  cat <<-EOTOML > Rocket.toml
[development]
address = "localhost"
port = 8000
workers = 2
log = "normal"
secret_key = "$(openssl rand -base64 32)"

[production]
address = "0.0.0.0"
port = 8000
workers = 12
log = "normal"
secret_key = "$(openssl rand -base64 32)"
EOTOML
fi

# Setup complete
infoMsg "Setup is complete, you may run the development server with:"
echo "fors start"
